<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Document</title>
</head>
<body>
  <div>
    <h2>一、属性的简写</h2>
    <div>ES6中，当对象键名与对应值名相等的时候，可以进行简写</div>
    <h2>二、属性名表达式</h2>
    <div>ES6 允许字面量定义对象时，将表达式放在括号内</div>
    <h2>三、super关键字</h2>
    <div>this关键字总是指向函数所在的当前对象，ES6 又新增了另一个类似的关键字super，指向当前对象的原型对象</div>
    <h2>四、扩展运算符的应用</h2>
    <div>在解构赋值中，未被读取的可遍历的属性，分配到指定的对象上面</div>
    <br>
    <div>注意：解构赋值必须是最后一个参数，否则会报错，解构赋值是浅拷贝</div>
    <br>
    <div>对象的扩展运算符等同于使用Object.assign()方法</div>
    <h2>五、属性的遍历</h2>
    <div>ES6 一共有 5 种方法可以遍历对象的属性。</div>
    <ul>
      <li>for...in：循环遍历对象自身的和继承的可枚举属性（不含 Symbol 属性）</li>
      <li>Object.keys(obj)：返回一个数组，包括对象自身的（不含继承的）所有可枚举属性（不含 Symbol 属性）的键名</li>
      <li>Object.getOwnPropertyNames(obj)：回一个数组，包含对象自身的所有属性（不含 Symbol 属性，但是包括不可枚举属性）的键名</li>
      <li>Object.getOwnPropertySymbols(obj)：返回一个数组，包含对象自身的所有 Symbol 属性的键名</li>
      <li>Reflect.ownKeys(obj)：返回一个数组，包含对象自身的（不含继承的）所有键名，不管键名是 Symbol 或字符串，也不管是否可枚举</li>
    </ul>
    <div>上述遍历，都遵守同样的属性遍历的次序规则：</div>
    <ul>
      <li>上述遍历，都遵守同样的属性遍历的次序规则：</li>
      <li>其次遍历所有字符串键，按照加入时间升序排列</li>
      <li>最后遍历所有 Symbol 键，按照加入时间升序排</li>
    </ul>
    <h2>六、对象新增的方法</h2>
    <div>关于对象新增的方法，分别有以下：</div>
    <ul>
      <li>Object.is()</li>
      <li>Object.assign()</li>
      <li>Object.getOwnPropertyDescriptors()</li>
      <li>Object.setPrototypeOf()，Object.getPrototypeOf()</li>
      <li>Object.keys()，Object.values()，Object.entries()</li>
      <li>Object.fromEntries()</li>
    </ul>
    <h4>Object.is()</h4>
    <div>严格判断两个值是否相等，与严格比较运算符（===）的行为基本一致，不同之处只有两个：一是+0不等于-0，二是NaN等于自身</div>
    <h4>Object.assign()</h4>
    <div>Object.assign()方法用于对象的合并，将源对象source的所有可枚举属性，复制到目标对象target。Object.assign()方法的第一个参数是目标对象，后面的参数都是源对象</div>
    <h4>Object.getOwnPropertyDescriptors()</h4>
    <div>返回指定对象所有自身属性（非继承属性）的描述对象</div>
    <h4>Object.setPrototypeOf()</h4>
    <div>Object.setPrototypeOf方法用来设置一个对象的原型对象</div>
    <br>
    <h4>Object.getPrototypeOf()</h4>
    <div>用于读取一个对象的原型对象</div>
    <h4>Object.keys()</h4>
    <div>返回自身的（不含继承的）所有可遍历（enumerable）属性的键名的数组</div>
    <h4>Object.values()</h4>
    <div>返回自身的（不含继承的）所有可遍历（enumerable）属性的键对应值的数组</div>
    <h4>Object.entries()</h4>
    <div>返回一个对象自身的（不含继承的）所有可遍历（enumerable）属性的键值对的数组</div>
    <h4>Object.fromEntries()</h4>
    <div>用于将一个键值对数组转为对象</div>
  </div>
  <script>
    // const baz = {foo:foo}
    // // 等同于
    // const baz = {foo}

    // Reflect.ownKeys({ [Symbol()]:0, b:0, 10:0, 2:0, a:0 })
    // ['2', '10', 'b', 'a', Symbol()]

    // setPrototypeOf 为对象设置原型链
    // const obj1 = {};
    // const obj2 = { foo: 'bar' };
    // Object.setPrototypeOf(obj1, obj2);

    // const { foo } = obj1;
    // foo // "bar"
    // 为obj1设置原型链是obj2
    // obj1的foo属性找不到，就找他的原型链obj2

    // 在解构赋值中，未被读取的可遍历的属性，分配到指定的对象上面
    // let { x, y, ...z } = { x: 1, y: 2, a: 3, b: 4 };
    // x // 1
    // y // 2
    // z // { a: 3, b: 4 }


    // let obj = { a: { b: 1 } };
    // // let { ...x } = obj;
    // obj.a.b = 2; // 修改obj里面a属性中键值
    // x.a.b // 2，影响到了结构出来x的值

    // console.log(Reflect.ownKeys({ [Symbol()]:0, b:0, 10:0, 2:0, a:0 }));
    // ['2', '10', 'b', 'a', Symbol()]


    // 严格判断两个值是否相等，与严格比较运算符（===）的行为基本一致，不同之处只有两个：一是+0不等于-0，二是NaN等于自身
    // +0 === -0 //true
    // NaN === NaN // false

    // Object.is(+0, -0) // false
    // Object.is(NaN, NaN) // true

    // const target = { a: 1, b: 1 };
    // const source1 = { b: 2, c: 2 };
    // const source2 = { c: 3 };

    // Object.assign(target, source1, source2);
    // target // {a:1, b:2, c:3} // 注意：Object.assign()方法是浅拷贝，遇到同名属性会进行替换

    // const obj = {
    //   foo: 123,
    //   get bar() { return 'abc' }
    // };

    // Object.getOwnPropertyDescriptors(obj)
    // { foo:
    //    { value: 123,
    //      writable: true,
    //      enumerable: true,
    //      configurable: true },
    //   bar:
    //    { get: [Function: get bar],
    //      set: undefined,
    //      enumerable: true,
    //      configurable: true } }


    // const obj = { foo: 'bar', baz: 42 };
    // console.log(Object.entries(obj));
    // [ ["foo", "bar"], ["baz", 42] ]


    // Object.fromEntries([
    //   ['foo', 'bar'],
    //   ['baz', 42]
    // ])
    // { foo: "bar", baz: 42 }
  </script>
</body>
</html>